/**
 * Created by liuchuanyang on 2018/8/27.
 */

import mutil from "../../utils/mutil";
import JsonSchemaGenerator from 'json-schema-generator';

export default {
    model: {
        prop: 'value',
        event: 'change'
    },
    props: {
        value: String,
        item: Object,
        page: Object,
        currentEleData: Object,
        // form: Object,
        currentNode: Object,
        elemNodes: [ Array ],
        /*isBg: {
            type: Boolean,
            default: false
        },*/
        dataset: Object,
        multiple: false,
    },
    data() {
        return {
            nvType: "iVar",
            nvValue: "",
            nvPath: "",
            nodeName: "",

            selectType: "tree",

            varDataTree: [],
            iVarDataTree: [],
            scopeDataTree: [],
            // staticDataTree: [],
            itemStaticDataTree: [],
            itemVarDataTree: [],
            itemMApiDataTree: [],
            itemFormDataTree: []
        }
    },
    mounted () {
        this.init();
        this.initValue()
    },
    computed: {
        renderDataTree() {
            if(this.nvType === 'var') {
                return this.varDataTree;
            } else if(this.nvType === 'iVar') {
                return this.iVarDataTree;
            } else if(this.nvType === 'scope') {
                return this.scopeDataTree;
            }

            let renderTree = [];

            return renderTree;
        },
        variables() {
            // 当前值，包含 { value, $index, index, row, itemState, state, datas, column, form }
            // scopeDataTree 要添加 scope.xxx , varDataTree 要添加 state.xxx, iVarDataTree 要添加 itemState.xxx
            let vars = [{ value: "value", label: "当前选择值", _label: "当前选择值" }, { value: "$index", label: "当前索引（0开始）", _label: "当前索引" }];
            let scopeDataTree = _.cloneDeep(this.scopeDataTree);
            let varDataTree = _.cloneDeep(this.varDataTree);
            let iVarDataTree = _.cloneDeep(this.iVarDataTree);

            // console.log(scopeDataTree, varDataTree, iVarDataTree)
            this.traverseTree(scopeDataTree, node => {
                // console.log("====>", node);
                node.value = `scope.${ node.rela || "" }`;
                node._label = node.value;
                node.prefix = "scope"
            });
            this.traverseTree(varDataTree, node => {
                node.value = `state.${ node.id || "" }`;
                node._label = node.value;
                node.prefix = "state"
            });
            this.traverseTree(iVarDataTree, node => {
                node.value = `itemState.${ node.id || "" }`;
                node._label = node.value;
                node.prefix = "itemState"
            });

            return _.concat(vars, scopeDataTree, varDataTree, iVarDataTree);
        },
        defExpandKeys() {   // 默认展开2层，并且 form & page 默认不展开
            let keys = [];

            if(this.renderDataTree && this.renderDataTree.length) {
                for(let i = 0; i < this.renderDataTree.length; i++) {
                    // console.log(this.renderDataTree[i]);
                    let node = this.renderDataTree[i];
                    // let prop = _.get(node, "prop");
                    let id = _.get(node, "id");
                    let subs = _.get(node, "children");

                    if(this._isFormPageNode(node)) {
                        continue;
                    }

                    keys.push(id);

                    if(subs && subs.length) {
                        for(let j = 0; j < subs.length; j++) {
                            let sNode = subs[j];
                            let sid = _.get(sNode, "id");
                            let sProp = _.get(sNode, "prop");
                            if(this._isFormPageNode(sNode)) {
                                continue;
                            }

                            keys.push(sid);

                            let tsubs = _.get(sNode, "children");

                            if(sProp === 'datas' && tsubs && tsubs.length === 1 && tsubs[0].prop === "") {
                                keys.push(tsubs[0].id);
                            }
                        }
                    }
                }
            }
            return keys;
        },
    },
    watch: {
        value(_value) {
            this.initValue();
        },
        nvValue(val) {
            if(this.isFormula) {
                this.$emit('change', val);
            } else {
                let fullValue = val;
                if(this.nvType && fullValue) fullValue = `${ this.nvType }:${ val }`;
                this.$emit('change', fullValue);
            }

        },
        item: {
            deep: true,
            handler() {
                this.init();
            }
        },
        dataset: {
            deep: true,
            handler() {
                this.init();
            }
        },
        'currentEleData._code': function(val) {
            // this.parse2info();
            // "var:name|a.b.c"
            // this.init();
            this.initValue();
            this.initScopeDataTree();
        },
        nodeName(name) {
            if(this.currentEleData) {
                this.currentEleData._name = name;

                if(this.currentNode && !this.currentNode.isRoot) {
                    this.currentNode.name = name;
                }
            }
        }
    },
    methods: {
        ...mutil,
        initValue(inValue) {
            let _value = inValue || this.value || "";

            // this.nvValue = newVal;
            if(this.isFormula) {
                // console.log(`------------------> `, _value)
                this.nvValue = _value;
                return ;
            }

            // let _value = "";
            let nvType = "";
            let nvValue = "";
            let nvPath = "";

            /*if(this.isBg) {
                _value = _.get(this.currentEleData, "_bg");
            } else {
                _value = _.get(this.currentEleData, "_value");
            }*/

            if(_value) {
                nvValue = _value;

                if(_.indexOf(_value, ":") >= 0) {
                    let arrs = _value.split(":");
                    if(arrs && arrs.length > 1) {
                        nvType = _.get(arrs, '[0]');
                        nvValue = _.get(arrs, '[1]')
                    }
                }

                if(nvValue && _.indexOf(nvValue, '|') >= 0) {
                    let arrs = _value.split("|");
                    if(arrs && arrs.length > 1) {
                        nvValue = _.get(arrs, '[0]');
                        nvPath = _.get(arrs, '[1]')
                    }
                }
            }

            this.nvType = nvType || (this.hasForEleNode() ? "scope": "iVar");    // !this.isModelNode(this.currentEleData) ?
            this.nvValue = nvValue;
            this.nvPath = nvPath;
            this.nodeName = _.get(this.currentEleData, "_name");
        },
        init() {
            this.initVarDataTree();
            this.initIVarDataTree();
            this.initScopeDataTree();
        },
        traverseTree(nodeList, fn) {
            if (_.isArray(nodeList) && !_.isEmpty(nodeList)) {
                _.forEach(nodeList, child => {
                    // child.prefix = "scope";
                    if(typeof fn === 'function') fn(child)
                    this.traverseTree(child.children, fn); // 递归遍历子节点
                });
            } else if(nodeList && !_.isArray(nodeList) && _.isObject(nodeList)) {
                if(typeof fn === 'function') fn(nodeList);
                this.traverseTree(nodeList.children, fn);
            }
        },
        _isFormPageNode(node) {
            let prop = _.get(node, "prop");
            // let id = _.get(node, "id");
            let subs = _.get(node, "children");
            let fIdx = _.findIndex(subs, { prop: "form_id" });
            let pIdx = _.findIndex(subs, { prop: "pageSize" });

            return (prop === 'form' && fIdx >= 0) || (prop === 'page' && pIdx >= 0);
        },
        schemaToTree(schema, parent, propName) {
            let parentId = _.get(parent, "id") || "";
            let parentRela = _.get(parent, "rela") || "";
            let id = "";
            let rela = "";

            if(propName === '[0]') {
                id = parentId ? `${ parentId }${ propName }`: propName;
                rela = "";
            } else if(propName) {
                id = parentId ? `${ parentId }.${ propName }`: propName;
                rela = parentRela ? `${ parentRela }.${ propName }`: propName;
            }

            let node = { label: _.get(schema, 'title'), id, rela };

            // 保存简要描述信息
            /*if (schema.description) {
                node.description = schema.description;
            }*/

            // 处理类型及其它字段
            switch (schema.type) {
                case "object":
                    node.children = [];
                    for (let key in schema.properties) {
                        let childSchema = schema.properties[ key ];
                        let title = _.get(childSchema, "title") || "";
                        let child = this.schemaToTree(childSchema, node, key);
                        let label = key;

                        if(title) {
                            label = title;
                        }

                        child.label = label || key;    // `${ childLabel }[${ key }]`;
                        child.type = _.get(childSchema, "type");
                        child.prop = key;
                        node.children.push(child);
                    }
                    // 处理required属性
                    if (schema.required && schema.required.length > 0) {
                        node.required = schema.required;
                    }
                    // form数据树个性化树节点顺序， datas 排第一
                    if(_.findIndex(node.children, { prop: 'form'}) >= 0 &&
                        _.findIndex(node.children, { prop: 'page'}) >= 0 &&
                        _.findIndex(node.children, { prop: 'datas'}) >= 0) {
                        // 将 datas提前
                        let dIdx = _.findIndex(node.children, { prop: 'datas'});

                        if(dIdx > 0) {
                            let dArr = node.children.splice(dIdx, 1);
                            node.children = _.concat(dArr, node.children);
                        }
                    }
                    break;
                case "array":
                    if(!schema.items.type) schema.items.type = 'object';
                    let child = this.schemaToTree(schema.items, node, '[0]');

                    child.label = `行记录`;
                    child.type = _.get(schema.items, "type");
                    child.prop = "";
                    node.children = [ child ];
                    node.type = "array";
                    break;
                default:
                    node.type = schema.type;
                    break;
            }

            return node;
        },
        initVarDataTree() {
            let varDataTree = [];
            let vars = _.get(this.page, "vars");
            let varVals = {};

            if(vars && vars.length) {
                for(let i = 0; i < vars.length; i++) {
                    let iv = vars[ i ];
                    let prop = _.get(iv, "prop");
                    if(prop) {
                        varVals[ prop ] = _.get(this.dataset, `state.${ prop }`);
                    }
                }

                let varSchema = JsonSchemaGenerator(varVals);
                let root = this.schemaToTree(varSchema);

                varDataTree = _.get(root, "children", []);
            }

            this.varDataTree = varDataTree;
        },
        initIVarDataTree() {
            let iVarDataTree = [];
            let vars = _.get(this.item, "vars");
            let varVals = {};
            let itemCode = _.get(this.item, "alias") || _.get(this.item, "page_item_code");

            if(vars && vars.length) {
                for(let i = 0; i < vars.length; i++) {
                    let iv = vars[ i ];
                    let prop = _.get(iv, "prop");
                    if(prop) {
                        varVals[ prop ] = _.get(this.dataset, `items.${ itemCode }.${ prop }`);
                    }
                }

                let varSchema = JsonSchemaGenerator(varVals);
                let root = this.schemaToTree(varSchema);

                iVarDataTree = _.get(root, "children", []);
            }

            this.iVarDataTree = iVarDataTree;
        },
        initScopeDataTree() {
            // 获取最近的 multiple 节点
            let code = _.get(this.currentEleData, "_code");

            if(!code) return;

            let nodeParents = this.$utils.getTreePath(code, this.elemNodes, 'code', 'children', true);
            let multiNodes = _.filter(nodeParents, np => mutil.isMultipleNode(_.get(np, "def")));
            let renderTree = [];

            if(multiNodes && multiNodes.length) {
                let realRenderTree = renderTree;

                for(let i = 0; i < multiNodes.length; i++) {
                    let mn = multiNodes[ i ];
                    let value = _.get(mn, `def._value`);
                    // let nvType = "scope";
                    let nvValue = "";

                    // console.log(`--------------> value: `, value, realRenderTree)

                    if(value) {
                        nvValue = value;

                        if(_.indexOf(value, ":") >= 0) {
                            let arrs = _.split(value, ":");
                            let parentNvType = _.get(arrs, "[0]");
                            nvValue = _.get(arrs, "[1]");

                            if(parentNvType === 'var') {
                                realRenderTree = this.varDataTree
                            } else {
                                realRenderTree = this.iVarDataTree
                            }
                        } else {
                            realRenderTree = this.iVarDataTree
                        }

                        let subTreeNode = this.$utils.getTreeData(realRenderTree, "rela", nvValue);

                        if(subTreeNode) {
                            realRenderTree = [ subTreeNode ];
                        } else {
                            realRenderTree = [];
                            break;
                        }
                    }
                }

                this.scopeDataTree = realRenderTree;
            }
        },
        hasForEleNode() {
            let code = _.get(this.currentEleData, "_code");
            let nodeParents = this.$utils.getTreePath(code, this.elemNodes, 'code', 'children', true);
            let multiNodes = _.filter(nodeParents, np => mutil.isMultipleNode(_.get(np, "def")));

            return multiNodes && multiNodes.length > 0;
        },
        handleSelectTreePath(data) {
            let type = _.get(data, "type");
            let isMultiple = this.multiple || mutil.isMultipleNode(this.currentEleData)

            if(isMultiple && type !== 'array') {
                return this.$jui.toast("循环节点，需选择 [ array ] 类型数据。");
            } else if(!isMultiple && type === 'array') {
                return this.$jui.toast("普通节点，不支持 [ array ] 类型数据。");
            }

            let val = "";

            if(this.nvType === 'scope') {
                if(this.hasForEleNode()) {
                    val = _.get(data, "rela");
                } else {
                    val = _.get(data, "id");

                    let datasPathDef = _.get(this.item, 'data_fieldsmap._rowsPath');

                    if(!datasPathDef) {
                        datasPathDef = "datas";
                    }

                    if(val) val = val.replace(new RegExp(`^${ datasPathDef }`), "");
                    // 去除默认的 datas
                }
            } else {
                val = _.get(data, "id");
            }

            if(val) this.nvValue = val;

            // this.handleChgNv();
        }
    }
};
